#include "playvoice.h"
#include <QDebug>
#include <QCoreApplication>
#include "MsgManage.h"
#include "model/modelmsg.h"
#include "mylogger.h"
#include <QFile>
#include <QSettings>
#include "lightcontrol.h"

using namespace ns_yht;

PlayVoice *PlayVoice::m_instance = nullptr;

PlayVoice::PlayVoice()
{
    m_instance = this;
    QSettings *setting = new QSettings(QCoreApplication::applicationDirPath() + "/setting.ini", QSettings::IniFormat);
    m_filterMode = setting->value("FilterMode", 0).toInt();
}

PlayVoice::~PlayVoice()
{
    if (m_timerId > 0)
        killTimer(m_timerId);
    m_timerId = 0;
    if (m_instance)
    {
        m_instance->deleteLater();
        m_instance = nullptr;
    }
}

PlayVoice *PlayVoice::instance()
{
    return m_instance;
}

void PlayVoice::start()
{
    if (m_timerId == 0)
        m_timerId = startTimer(5000);
}

void PlayVoice::play(VoiceType type, quint64 id)
{
    const QString voiceFile = getVoiceFile(type, id);
    const QString fullFile = QCoreApplication::applicationDirPath() + "/voice/" + voiceFile;
    if (voiceFile.isEmpty() || !QFile::exists(fullFile))
    {
        if (GLOG)
            GLOG->info("voice file not exist: {}", voiceFile.toStdString());
        return;
    }
    if (GLOG)
        GLOG->debug("play voice file:{}", voiceFile.toStdString());
    m_lastVoiceTime = QDateTime::currentSecsSinceEpoch();
#if defined(Q_OS_LINUX)
    if (m_process == nullptr)
    {
        m_process = new QProcess(this);
        connect(m_process, &QProcess::errorOccurred, this, &PlayVoice::onProcessError);
        m_process->setWorkingDirectory(QCoreApplication::applicationDirPath() + "/voice/");
        m_process->start("bash");
    }
    // QString args = QString("aplay -D plughw:0,0 -d3 '%1' \n").arg(voiceFile); //定线制水域会截断
    QString args = QString("aplay  '%1' \n").arg(voiceFile);
    m_process->write(args.toUtf8());
#endif
#if defined(Q_OS_WIN)
    QString cmd = QString("start wmplayer.exe \"%1\"").arg(fullFile);
    // system(cmd.toLatin1());
#endif
}

void PlayVoice::OnstandardOutput(QByteArray result)
{
    qInfo() << "PlayVoice::OnstandardOutput";
}

void PlayVoice::onProcessError(QProcess::ProcessError error)
{
    GLOG->info("play voice process error {}", int(error));
}

void PlayVoice::timerEvent(QTimerEvent *event)
{
    m_msgModel = MSGMANAGE->getNextMsg();
    if (m_msgModel != nullptr)
    {
        LIGHTTASK->startShrink(LightColor::Red);
        if (m_msgModel->type == AlertType::type_shipCollision)
            play(VoiceType::Collision);
        else if (m_msgModel->type == AlertType::type_riskarea)
        {
            play(VoiceType::RiskArea, m_msgModel->ID - 1);
        }
    }
    else
    {
        bool exists = MSGMANAGE->hasMsg();
        if (exists)
            LIGHTTASK->startShrink(LightColor::Red);
        else
        {
            LIGHTTASK->stopShrink(LightColor::Red);
            LIGHTTASK->turnOn(LightColor::Red, false);
        }
        if (QDateTime::currentSecsSinceEpoch() - m_lastVoiceTime >= 1800)
        {
            play(VoiceType::SystemRunning);
        }
    }
}

QString PlayVoice::getVoiceFile(VoiceType type, int id)
{
    switch (type)
    {
    case VoiceType::SystemStart:
        return "system start.WAV";
    case VoiceType::SystemRunning:
        return "system running.WAV";
    case VoiceType::NetworkConnected:
        return "network connected.WAV";
    case VoiceType::NetworkDisconnected:
        return "network disconnected.WAV";
    case VoiceType::TokenReceived:
        return "token received.WAV";
    case VoiceType::TokenFailed:
        return "token failed.WAV";
    case VoiceType::SystemClose:
        return "system close.WAV";
    case VoiceType::StartSystemUpdate:
        return "start system update.WAV";
    case VoiceType::SystemUpdateSucceed:
        return "system update succeed.WAV";
    case VoiceType::SystemUpdateFailed:
        return "system update failed.WAV";
    case VoiceType::StartRiskAreaUpdate:
        return "start riskarea update.WAV";
    case VoiceType::RiskAreaUpdateSucceed:
        return "riskarea update succeed.WAV";
    case VoiceType::RiskAreaUpdateFailed:
        return "riskarea update failed.WAV";
    case VoiceType::BluetoothConnected:
        return "bluetooth connected.WAV";
    case VoiceType::BluetoothDisconnected:
        return "bluetooth disconnected.WAV";
    case VoiceType::BluetoothFailed:
        return "bluetooth failed.WAV";
    case VoiceType::BluetoothWaiting:
        return "bluetooth waiting.WAV";
    case VoiceType::BluetoothClose:
        return "bluetooth close.WAV";
    case VoiceType::BridgePass:
        return "bridge pass.WAV";
    case VoiceType::DutyCaution:
        return "duty caution.WAV";
    case VoiceType::Collision:
        return QString("collision_%1.WAV").arg(m_filterMode);
    case VoiceType::RiskArea:
        if (id < 0)
            return "riskarea.WAV";
        else
            return QString("riskarea_%1.WAV").arg(id);
    default:
        return "";
    }
}

void PlayVoice::ensureCurrentMsgModel()
{
    if (m_msgModel)
    {
        MSGMANAGE->ensure(m_msgModel);
    }
}